package com.gopay.checkorder.service.impl;

import java.math.BigDecimal;
import java.util.List;

import javax.annotation.Resource;

import org.apache.commons.lang.builder.ToStringBuilder;
import org.apache.commons.lang.builder.ToStringStyle;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.gopay.checkorder.service.BankOrderService;
import com.gopay.checkorder.service.task.BankCountDownLatch;
import com.gopay.common.Result;
import com.gopay.common.constants.bank.BankConstants;
import com.gopay.common.constants.bank.BisBankBusinessProd;
import com.gopay.common.constants.bank.BisBankInterfaceChannel;
import com.gopay.common.constants.bank.BocomConstants;
import com.gopay.common.constants.bank.BocomOrderStatus;
import com.gopay.common.constants.proccode.ProcCodeConstants;
import com.gopay.common.domain.bank.BankOrder;
import com.gopay.common.domain.bank.BaseMessage;
import com.gopay.common.domain.bank.bocom.ebank.pay.BocomB2bMessage;
import com.gopay.common.domain.bank.bocom.ebank.pay.BocomB2bQueryDetail;
import com.gopay.common.domain.bank.bocom.ebank.pay.b2b.req.BocomB2bReq;
import com.gopay.common.domain.bank.dayend.BaseDayendEntry;
import com.gopay.common.domain.cashier.BankCardType;
import com.gopay.common.domain.cps.vo.CheckOrderResult;
import com.gopay.common.domain.cps.vo.InAccInfo;
import com.gopay.remote.bank.BankInteractRemoteService;

public class CheckOrderBocomB2bImpl implements BankOrderService {
	private final static Logger logger = LoggerFactory.getLogger("BOCOM");

	@Resource(name = "bankClient")
	private BankInteractRemoteService bankClient;
	@Override
	public CheckOrderResult checkOrder(BankOrder bankOrder, String target) {
		CheckOrderResult checkOrderResult = new CheckOrderResult();
		checkOrderResult.setSuccess(false);
		checkOrderResult.setOrderId(bankOrder.getOrderId());
		try {
			BocomB2bReq base = new BocomB2bReq();
			base.setOrderId(bankOrder.getOrderId());
			base.setBankOrderId(bankOrder.getOutOrderId());
			base.setBank(BankConstants.BANK_LOGO_BOCOM);
			base.setBankIntrChann(BisBankInterfaceChannel.get(bankOrder.getInterfaceChennelCode()));
			base.setBankBusProd(BisBankBusinessProd.get(bankOrder.getBankBizProdCode()));
			
			Result result = new Result();
			result = bankClient.query(base);

			if (result == null || !result.isSuccess() || result.getDefaultModel() == null) {
				logger.error("bankClient fail.");				
				if(result ==null || ProcCodeConstants.PROC_CODE_100E6037.equals(result.getResultCode())){
					BankCountDownLatch.failIncrease(bankOrder.getBankCode());
					checkOrderResult.setCommunicateError(true);
				}
				logger.error(ToStringBuilder.reflectionToString(result,ToStringStyle.DEFAULT_STYLE));
				checkOrderResult.setErrCode(ProcCodeConstants.PROC_CODE_100E5062);
				checkOrderResult.setErrMsg("系统返回对账结果为空");
				return checkOrderResult;
			}

			BocomB2bReq res = (BocomB2bReq) result.getDefaultModel();
			if (res == null || res.getRetCode() == null) {
				// 查询订单为空
				logger.error("fail:orderId:" + bankOrder.getOrderId()+ " errcode:" + ProcCodeConstants.PROC_CODE_100E5062+ " err:bis query is null.");
				checkOrderResult.setErrCode(ProcCodeConstants.PROC_CODE_100E5062);
				checkOrderResult.setErrMsg("银行返回对账结果为空");
				return checkOrderResult;
			}
			// 通信状态码错误
			if (!res.getRetCode().equals(BocomConstants.RSPTYPE_SUCCESS)) {
				logger.error("BOCOM B2B bankClient fail. errorCode:"+ res.getRetCode() + "，errorMsg:："+ res.getErrorMessage() + "，orderId："+ bankOrder.getOrderId());
				checkOrderResult.setErrCode(ProcCodeConstants.PROC_CODE_100E5062);
				checkOrderResult.setErrMsg(res.getErrorMessage());
				return checkOrderResult;
			}
			if (res.getRetCode() != null && !res.getRetCode().equals(BocomConstants.RSPTYPE_SUCCESS)) {
				// 查询订单错误
				logger.error("fail:orderId:" + bankOrder.getOrderId()+ " errcode:" + res.getRetCode() + " err:"+ res.getErrorMessage());
				checkOrderResult.setErrCode(ProcCodeConstants.PROC_CODE_100E5062);
				checkOrderResult.setErrMsg(res.getErrorMessage());
				return checkOrderResult;
			}
			if (res.getQueryDetails() != null && res.getQueryDetails().size() != 0) {
				BocomB2bQueryDetail orderRes = res.getQueryDetails().get(0);
				checkOrderResult.setOrderId(orderRes.getOrder());
				checkOrderResult.setAmount(new BigDecimal(orderRes.getAmount()));
				
				//成功处理
				if (orderRes.getOrderState().equals(BocomConstants.TRANSTATE_SUCCESS)) {
					logger.error("交通银行B2B订单:" + orderRes.getOrder()+ ",交易返回信息:已支付,查到的订单状态:" + orderRes.getOrderState());
					checkOrderResult.setSuccess(true);
					InAccInfo accInfo = new InAccInfo();
					accInfo.setOrderId(orderRes.getOrder());
					accInfo.setAmount(new BigDecimal(orderRes.getAmount()));
					accInfo.setRetCode("00");
					accInfo.setCardType(BankCardType.Unknown.toString());
					checkOrderResult.setAccInfo(accInfo);
				}
				//处理中
				else if(orderRes.getOrderState().equals(BocomConstants.TRANSTATE_PROCESSING)){
					logger.error("交通银行B2B订单:" + orderRes.getOrder()+ ",交易返回失败信息:处理中,查到的订单状态:"+ orderRes.getOrderState());
					checkOrderResult.setErrMsg("处理中");
				}
				// 失败处理
				else if (orderRes.getOrderState().equals(BocomConstants.TRANSTATE_FAIL)) {
					logger.error("交通银行B2B订单:" + orderRes.getOrder()+ ",交易返回失败信息:支付失败,查到的订单状态:"+ orderRes.getOrderState());
     				checkOrderResult.setBankFailure(true);
					checkOrderResult.setErrMsg("支付失败");
				}
				//不处理
				else {
					logger.error("交通银行B2B订单:"+ orderRes.getOrder() + ",暂不进行账务处理,查到的订单状态:" + orderRes.getOrderState());
					checkOrderResult.setErrMsg("订单状态不明");
				}
			}else{
				logger.error("交通银行B2B交易返回成功状态,但无任何订单信息（有可能银行方面问题）暂不进行账务处理,交易码 = "+ bankOrder.getOrderId());
				checkOrderResult.setErrMsg("银行返回订单未查到");
			}
			return checkOrderResult;
		} catch (Exception e) {
			logger.error("bocom b2b bankorder fail.", e);
			checkOrderResult.setErrCode(ProcCodeConstants.PROC_CODE_100E5062);
			return checkOrderResult;
		}
	}

	public BankInteractRemoteService getBankClient() {
		return bankClient;
	}

	public void setBankClient(BankInteractRemoteService bankClient) {
		this.bankClient = bankClient;
	}

	@Override
	public BankOrder getDbOrder() {
		// TODO Auto-generated method stub
		return null;
	}

	@Override
	public BaseMessage dayend(String bank_bus) {
		// TODO Auto-generated method stub
		return null;
	}

	@Override
	public List<CheckOrderResult> checkDayend(String bank_bus) {
		// TODO Auto-generated method stub
		return null;
	}

	@Override
	public Result getDayendMsg(String string) {
		// TODO Auto-generated method stub
		return null;
	}

	@Override
	public CheckOrderResult checkDayendOrder(BaseDayendEntry bdm, BankOrder bo) {
		// TODO Auto-generated method stub
		return null;
	}
}
